﻿
using Castle.Core.Internal;
using Coldairarrow.Entity.Base_Manage;
using Coldairarrow.Entity.Interface;
using Coldairarrow.Util;
using Microsoft.EntityFrameworkCore.Metadata;
using NetTopologySuite.Geometries;
using Newtonsoft.Json.Linq;
using System;
using System.Collections;
using System.Collections.Generic;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Linq.Dynamic.Core;
using System.Threading;
using System.Threading.Tasks;

namespace Coldairarrow.Business.Interface
{
    public class InvInterfaceBusiness : Interface_BaseBusiness, IJob_Business, ITransientDependency
    {

        public List<OL_FilterDTO> Filters;

        public int NoQueryNum { get; set; }
        public InvInterfaceBusiness()
        {
            this.InterfaceName = "乐歌库存查询";
            //获取主键字段列表


            //获取字段的映射关系
            tableField = GetMapField("addRow");

            //索引字段
            Keys = GetKeys("addRow");
            indexFields.Add(Keys.Where(X => X.Type == "K").First().Field);
            //查询过滤条件
            Filters = new List<OL_FilterDTO>();


            //查询执行中的事件
            OnQueryEvent += InterfaceBusiness_OnQueryEvent;
            //查询执行前的事件
            BeforeQueryEvent += InterfaceBusiness_BeforeQueryEvent;
            //执行非查询请求中的事件
            OnNoQueryEvent += InterfaceBusiness_OnNoQueryEvent;
        }

        /// <summary>
        /// 执行非查询请求中时间
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="noQueryEventArgs"></param>
        private void InterfaceBusiness_OnNoQueryEvent(object sender, NoQueryEventArgs noQueryEventArgs)
        {
            //API请求是否成功
            noQueryEventArgs.Success = noQueryEventArgs.Result["success"].ToString().ToBool();
        }


        /// <summary>
        /// 查询执行前的事件
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="queryEventArgs"></param>
        private void InterfaceBusiness_BeforeQueryEvent(object sender, QueryEventArgs queryEventArgs)
        {
            //执行查询前添加过滤条件
            if (queryEventArgs.Page.Filters.IsNullOrEmpty() && !Filters.IsNullOrEmpty())
            {
                queryEventArgs.Page.Filters = Filters;
            }
        }

        /// <summary>
        /// 查询执行中的事件
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="queryEventArgs"></param>
        private void InterfaceBusiness_OnQueryEvent(object sender, QueryEventArgs queryEventArgs)
        {
            //是否查询完成
            if (queryEventArgs.Result["data"]["rows"].ToList().Count == 0)
            {
                queryEventArgs.Page.Complete = true;
            }
            //向总行中添加新的行
            queryEventArgs.Rows.AddRange(queryEventArgs.Result["data"]["rows"].ToList());
            //获取总页数
            queryEventArgs.Page.Total = queryEventArgs.Result["data"]["total"].ToString().ToInt();
            //获取查询成功标志
            queryEventArgs.Success = queryEventArgs.Result["success"].ToString().ToBool();
        }

        /// <summary>
        /// 新增更新表
        /// </summary>
        public async void ExecuteInterface()
        {

            try
            {
                //数据库连接
                ConString = JsonSettingHelper.GetSetting("Database:BaseDb:ConnectionString");
                SqlDb = (SqlServerHelper)DbHelperFactory.GetDbHelper(EFCore.Sharding.DatabaseType.SqlServer, ConString);

                //获取此接口的所有API信息
                this.interfaceOption = SqlDb.GetListBySql<Base_InterfaceOption>(@$"SELECT  * FROM  Base_InterfaceOption(NOLOCK) WHERE Name='{InterfaceName}' ");
                Base_InterfaceOption queryOption = this.interfaceOption.Where(o => o.OperateType == "getFilterRows").First();//查询API配置
                Base_InterfaceOption insertOption = this.interfaceOption.Where(o => o.OperateType == "addRow").First();//新增API配置
                Base_InterfaceOption upDateOption = this.interfaceOption.Where(o => o.OperateType == "editRow").First();//更行API配置
                Base_InterfaceOption deleteOption = this.interfaceOption.Where(o => o.OperateType == "deleteRow").First();//删除API配置



                //获取库存信息
                LG_InvInterfaceBusiness LG_Inv = new LG_InvInterfaceBusiness();
                List<LGInventory> sourceData = await LG_Inv.QueryAsync<LGInventory>(LG_Inv.LG_Query, this.SqlDb);//源数据集合
                //批次库存（库龄）信息
                LG_LGInventoryBatchBusiness LG_InvBatc = new LG_LGInventoryBatchBusiness();
                List<LGInventoryBatch> LGInventoryBatchList = await LG_InvBatc.QueryAsync<LGInventoryBatch>(LG_InvBatc.LG_Query, this.SqlDb);//源数据集合

                sourceData.ForEach(x =>
                {
                    x.ID = x.goodsCode + x.warehouseCode;
                    //等级
                    if (x.goodsLevel == "101301") x.goodsLevel = "良品";
                    else if (x.goodsLevel == "101302") x.goodsLevel = "等级品";
                    else if (x.goodsLevel == "101303") x.goodsLevel = "残次品";
                    else x.goodsLevel = "";
                    //效期状态
                    if (x.validStatus == "101701") x.validStatus = "未临期";
                    else if (x.validStatus == "101702") x.validStatus = "临期";
                    else if (x.validStatus == "101703") x.validStatus = "过期";
                    else x.validStatus = "无效期";

                    var age = LGInventoryBatchList.Where(y => y.warehouseCode == x.warehouseCode && y.goodsCode == x.goodsCode);
                    x.goodsCode = x.goodsCode.Replace("_", ".");

                    //row.cnName = first.cnName;
                    //row.goodsCode = first.goodsCode.Replace("_", ".");
                    //row.lecangsCode = first.lecangsCode;
                    //row.warehouseCode = first.warehouseCode;
                    //row.goodsNum = item1.Sum(x => x.goodsNum.ToDouble()).ToString("F2");
                    if (!age.IsNullOrEmpty() && age.Count() > 0)
                    {
                        var age0_90 = age.Where(x => 0 <= x.inventoryAge.ToInt() && 90 >= x.inventoryAge.ToInt());
                        x.age0_90 = age0_90.IsNullOrEmpty() || age0_90.Count() == 0 ? 0 : age0_90.Sum(x => (decimal)x.goodsNum.ToDouble());

                        var age91_180 = age.Where(x => 91 <= x.inventoryAge.ToInt() && 180 >= x.inventoryAge.ToInt());
                        x.age91_180 = age91_180.IsNullOrEmpty() || age91_180.Count() == 0 ? 0 : age91_180.Sum(x => (decimal)x.goodsNum.ToDouble());

                        var age181_270 = age.Where(x => 181 <= x.inventoryAge.ToInt() && 270 >= x.inventoryAge.ToInt());
                        x.age181_270 = age181_270.IsNullOrEmpty() || age181_270.Count() == 0 ? 0 : age181_270.Sum(x => (decimal)x.goodsNum.ToDouble());

                        var age271_365 = age.Where(x => 271 <= x.inventoryAge.ToInt() && 365 >= x.inventoryAge.ToInt());
                        x.age271_365 = age271_365.IsNullOrEmpty() || age271_365.Count() == 0 ? 0 : age271_365.Sum(x => (decimal)x.goodsNum.ToDouble());

                        var age365_ = age.Where(x => 365 < x.inventoryAge.ToInt());
                        x.age365_ = age365_.IsNullOrEmpty() || age365_.Count() == 0 ? 0 : age365_.Sum(x => (decimal)x.goodsNum.ToDouble());

                        x.HighAge = x.age181_270 + x.age271_365 + x.age365_;
                    }


                });
                sourceData.GroupBy(x => x.ID).ForEach(x =>
                {
                    if (x.Count() > 1)
                    {
                        int c = 0;
                        foreach (var item1 in x)
                        {
                            c++;
                            item1.ID = item1.ID + c;
                        }
                    }


                });
                //获取需要删除的数据
                List<LGInventory> targetData = new List<LGInventory>();//目标据集合
                Filters.Clear();
                Filters.Add(
                new OL_FilterDTO() { ControlId = "", DataType = 15, SpliceType = 1, FilterType = 14, Value = "" }//F_MO_APPROVEDATE字段过滤单日开始700天前到现在的数据
            );
                targetData = await QueryAsync<LGInventory>(queryOption, tableField, SqlDb);



                if (sourceData.Count > 0 && this.State > 0)
                {


                    //更新
                    #region
                    List<LGInventory> updataItem = sourceData.Intersect(targetData, new ComparerFromKeys<LGInventory>(Keys, "RowId")).ToList();//获取交集(更新项)
                    List<OL_RowDTO> updataData = ConvertOL_Row(updataItem, tableField);//需要更新的数据集合
                    ExecuteNoQuery<OL_RowDTO>(updataData, upDateOption, SqlDb);//执行更新
                    #endregion

                    //新增
                    #region
                    List<LGInventory> insertItem = sourceData.Except(targetData, new ComparerFromKey<LGInventory>(indexFields.First(), "RowId")).ToList();//获取源数据对目标数据的差集(新增项)
                    List<OL_RowDTO> insertData = ConvertOL_Row(insertItem, tableField);//需要新增的数据集合
                    ExecuteNoQuery<OL_RowDTO>(insertData, insertOption, SqlDb);//执行插入行
                    #endregion


                    //删除
                    #region
                    List<LGInventory> deleteItem = targetData.Except(sourceData, new ComparerFromKey<LGInventory>(indexFields.First(), "RowId")).ToList();//获取目标数对据源数据的差集(删除项)
                    List<OL_RowDTO> deleteData = ConvertOL_Row(deleteItem, tableField);//需要删除的数据集合
                    ExecuteNoQuery<OL_RowDTO>(deleteData, deleteOption, SqlDb);//执行删除行
                    //需要删除的不删除，数量更改为0
                    //foreach (var item1 in deleteItem)
                    //{

                    //    item1.onWayNum = "0";
                    //    item1.pendingNum = "0";
                    //    item1.goodsNum = "0";
                    //    item1.blockedNum = "0";
                    //    item1.uesNum = "0";
                    //    sourceData.Add(item1);
                    //}

                    //同步数据库
                        SqlDBInterfaceBusiness sqlDBInterface = new SqlDBInterfaceBusiness(Keys);
                        sqlDBInterface.ExecuteInterface<LGInventory>(sourceData, "SD_LG_LGInventory");
                    #endregion



                }
                else
                {
                    throw new Exception("目标/源查询无数据无法执行接口!!");
                }

            }
            catch (Exception ex)
            {
                AddLog(SqlDb, ex.Message, InterfaceName, "erro", "");
            }
        }


        /// <summary>
        /// 将源数据根据字典映射关系转换成OL_RowDTO
        /// </summary>
        /// <typeparam name="T">源数据</typeparam>
        /// <param name="sourceData">源数据</param>
        /// <param name="map">Key为目标字段名称，Value为源字段名称</param>
        /// <returns></returns>
        public List<OL_RowDTO> ConvertOL_Row<T>(List<T> sourceData, Dictionary<string, string> map)
        {
            List<OL_RowDTO> list = new List<OL_RowDTO>();
            object rowId;
            foreach (var item in sourceData)
            {
                rowId = item.GetPropertyValue("RowId");
                //需要新增的数据
                OL_RowDTO row = new OL_RowDTO() { RowId = rowId.IsNullOrEmpty() ? null : rowId.ToString(), Controls = new List<Control>() };
                foreach (var c in map)
                {
                    //判断对象的字段是否存在
                    if (item.ContainsProperty(c.Value))
                    {
                        //存在则添加数据
                        row.Controls.Add(new Control() { ControlId = c.Key, Value = item.GetPropertyValue(c.Value) });
                    }
                }
                list.Add(row);
            }
            return list;
        }

        /// <summary>
        /// 任务
        /// </summary>
        public void Job()
        {
            ExecuteInterface();
        }
    }



}
